package com.repair.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.repair.entity.Announcement;
import com.repair.entity.AnnouncementRead;
import com.repair.mapper.AnnouncementMapper;
import com.repair.mapper.AnnouncementReadMapper;
import com.repair.service.AnnouncementService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

@Service
public class AnnouncementServiceImpl extends ServiceImpl<AnnouncementMapper, Announcement> implements AnnouncementService {
    
    @Autowired
    private AnnouncementMapper announcementMapper;
    
    @Autowired
    private AnnouncementReadMapper announcementReadMapper;
    
    @Override
    @Transactional
    public Announcement create(Announcement announcement) {
        announcementMapper.insert(announcement);
        return announcement;
    }
    
    @Override
    @Transactional
    public void update(Announcement announcement) {
        announcementMapper.update(announcement);
    }
    
    @Override
    @Transactional
    public void publish(Long id) {
        announcementMapper.updateStatus(id, 1);
    }
    
    @Override
    @Transactional
    public void offline(Long id) {
        announcementMapper.updateStatus(id, 2);
    }
    
    @Override
    public Announcement getById(Long id) {
        Announcement announcement = announcementMapper.findById(id);
        if (announcement != null) {
            announcementMapper.incrementViewCount(id);
        }
        return announcement;
    }
    
    @Override
    public List<Announcement> getLatest(int limit) {
        return announcementMapper.findLatest(limit);
    }
    
    @Override
    public List<Announcement> getByUserType(Integer userType) {
        return announcementMapper.findByUserType(userType);
    }
    
    @Override
    public List<Announcement> getAll() {
        return announcementMapper.findAll();
    }
    
    @Override
    @Transactional
    public void read(Long announcementId, Long userId) {
        if (!isRead(announcementId, userId)) {
            AnnouncementRead record = new AnnouncementRead();
            record.setAnnouncementId(announcementId);
            record.setUserId(userId);
            announcementReadMapper.insert(record);
        }
    }
    
    @Override
    public boolean isRead(Long announcementId, Long userId) {
        return announcementReadMapper.countByAnnouncementAndUser(announcementId, userId) > 0;
    }

    @Override
    public Announcement getLatestAnnouncement() {
        LambdaQueryWrapper<Announcement> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(Announcement::getStatus, 0)
                .orderByDesc(Announcement::getCreatedAt)
                .last("LIMIT 1");
        return getOne(wrapper);
    }

    @Override
    @Transactional
    public void createAnnouncement(Announcement announcement) {
        announcement.setStatus(0);
        save(announcement);
    }

    @Override
    @Transactional
    public void updateAnnouncement(Announcement announcement) {
        updateById(announcement);
    }

    @Override
    @Transactional
    public void deleteAnnouncement(Long id) {
        removeById(id);
    }
}